package com.aizuda.easyManagerTool.service.terminal.impl;

import cn.hutool.core.util.ObjectUtil;
import com.aizuda.easyManagerTool.domain.dto.terminal.SSHMessageDTO;
import com.jcraft.jsch.ChannelExec;
import com.jcraft.jsch.ChannelSftp;
import com.jcraft.jsch.ChannelShell;
import com.jcraft.jsch.Session;
import lombok.Data;
import lombok.extern.slf4j.Slf4j;

import java.util.Date;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;

@Data
@Slf4j
public class TerminalSessionManager {

    private static Map<String,Manager> terminalMap = new ConcurrentHashMap<>();

    public static Manager setGet(String key){
        return terminalMap.computeIfAbsent(key, k -> new Manager());
    }

    public static void remove(String key){
        terminalMap.remove(key);
    }

    public static Manager getManager(String key){
        return terminalMap.get(key);
    }

    public Session getSession(String key){
        return getManager(key).getSession();
    }

    public ChannelShell getChannelShell(String key){
        return getManager(key).getChannelShell();
    }

    public ChannelSftp getChannelSftp(String key){
        return getManager(key).getChannelSftp();
    }

    public void setThreadId(String key,Thread thread){
        getManager(key).setThread(thread);
    }

    public void destroyThread(String key){
        getManager(key).destroyThread();
    }


    @Data
    public static class Manager{
        private Session session;
        private ChannelShell channelShell;
        private ChannelSftp channelSftp;
        private ChannelExec channelExec;
        private ManagerLog managerLog = new ManagerLog();
        private Thread thread;

        private SSHMessageDTO sshMessageDTO;

        public void destroyThread(){
            if(ObjectUtil.isEmpty(thread)){
                return;
            }
            thread.interrupt();
            log.debug("中断执行成功 {}",thread.getId());
        }


        public void appendLog(String str){
            if(ObjectUtil.isEmpty(managerLog.getContent())){
                return;
            }
            managerLog.getContent().append(str);
        }

        public void createLog(Integer user,Integer tenantId,Integer server,String prefixPath){
            String path = prefixPath+tenantId+"-"+user+"-"+server+"-"+System.currentTimeMillis()+".txt";
            managerLog.setPath(path);
            managerLog.setContent(new StringBufferListener( this));
            managerLog.setUserId(user);
            managerLog.setTenantId(tenantId);
            managerLog.setServerId(server);
            managerLog.setStartTime(new Date());
        }

        public void endLog(){
            if(ObjectUtil.isNotEmpty(managerLog.getServerId())){
                managerLog.setEndTime(new Date());
            }
        }

        public void close(){
            if(ObjectUtil.isNotEmpty(this.getManagerLog().getContent())) {
                this.getManagerLog().getContent().onListener();
            }
            this.destroyThread();
            if(ObjectUtil.isNotEmpty(this.getSession())) {
                this.getSession().disconnect();
            }
            if(ObjectUtil.isNotEmpty(this.getChannelShell())) {
                this.getChannelShell().disconnect();
            }
            if(ObjectUtil.isNotEmpty(this.getChannelSftp())) {
                this.getChannelSftp().disconnect();
            }
        }

    }

    @Data
    public static class ManagerLog {
        private String path;
        private Integer serverId;
        private Integer userId;
        private Integer tenantId;
        private StringBufferListener content;
        private Date startTime;
        private Date endTime;
    }


}
